<template>
  <div v-loading.fullscreen.lock="fullscreenLoading">
    <div id="login">
      <div id="bgd">
        <canvas id="myCanvas" :width="width" :height="height"> </canvas>
      </div>
      <div id="loginBox">
        <h2>欢迎登录逛淘吧</h2>
        <el-tabs v-model="activeName" @tab-click="handleClick">
          <el-tab-pane label="登录" name="first">
            <el-form
              :model="loginForm"
              :rules="loginRules"
              ref="loginForm"
              label-width="0px"
            >
              <el-form-item label="" prop="userName" style="margin-top: 40px">
                <el-row>
                  <el-col :span="2">
                    <span class="el-icon-user-solid"></span>
                  </el-col>

                  <el-col :span="22">
                    <div class="c">
                      <el-input
                        class="inps"
                        placeholder="请输入用户名"
                        v-model="loginForm.userName"
                      ></el-input>
                      <el-select
                        v-model="value"
                        placeholder="请选择身份"
                        class="id_select"
                      >
                        <el-option
                          v-for="item in options"
                          :key="item.value"
                          :label="item.label"
                          :value="item.value"
                        >
                        </el-option>
                      </el-select>
                    </div>
                  </el-col>
                </el-row>
              </el-form-item>
              <el-form-item label="" prop="passWord">
                <el-row>
                  <el-col :span="2">
                    <span class="el-icon-lock"></span>
                  </el-col>
                  <el-col :span="22">
                    <el-input
                      class="inps"
                      placeholder="请输入密码"
                      v-model="loginForm.passWord"
                    ></el-input>
                  </el-col>
                </el-row>
              </el-form-item>

              <el-form-item label="" prop="yzm">
                <el-row>
                  <el-col :span="2">
                    <span class="el-icon-edit"></span>
                  </el-col>
                  <el-col :span="22">
                    <div class="a">
                      <el-input
                        class="inps"
                        placeholder="请输入验证码"
                        v-model="loginForm.yzm"
                      ></el-input>
                      <div class="s-canvas" @click="createdCode">
                        <canvas
                          id="s-canvas"
                          :width="contentWidth"
                          :height="contentHeight"
                        ></canvas>
                      </div>
                    </div>
                  </el-col>
                </el-row>
              </el-form-item>
              <div class="tips">
                <el-link type="white" @click="retrievePWD">忘记密码</el-link>
              </div>
              <el-form-item style="margin-top: 55px">
                <el-button
                  type="primary"
                  round
                  class="submitBtn"
                  @click="submitForm('loginForm')"
                  >登录</el-button
                >
              </el-form-item>
            </el-form>
          </el-tab-pane>
          <el-tab-pane label="商家注册" name="second">
            <admin-register></admin-register> </el-tab-pane
        ></el-tabs>
      </div>
    </div>
  </div>
</template>
<script>
import AdminRegister from "@/components/login/AdminRegister.vue";
export default {
  props: {
    fontSizeMin: {
      type: Number,
      default: 25,
    },
    fontSizeMax: {
      type: Number,
      default: 30,
    },
    backgroundColorMin: {
      type: Number,
      default: 255,
    },
    backgroundColorMax: {
      type: Number,
      default: 255,
    },
    colorMin: {
      type: Number,
      default: 0,
    },
    colorMax: {
      type: Number,
      default: 160,
    },
    lineColorMin: {
      type: Number,
      default: 100,
    },
    lineColorMax: {
      type: Number,
      default: 255,
    },
    dotColorMin: {
      type: Number,
      default: 0,
    },
    dotColorMax: {
      type: Number,
      default: 255,
    },
    contentWidth: {
      type: Number,
      default: 120,
    },
    contentHeight: {
      type: Number,
      default: 34,
    },
  },
  components: { AdminRegister },
  data() {
    var isTrue = (rule, value, callback) => {
      rule = value;
      if (this.identifyCode != this.loginForm.yzm) {
        callback(Error("您输入的验证码错误!"));
      }
    };
    return {
      options: [
        {
          value: "管理员",
          label: "管理员",
        },
        {
          value: "商家",
          label: "商家",
        },
      ],
      fullscreenLoading: false,
      value: "",
      nvf: "",
      identifyCode: "",
      activeName: "first",
      canvas: null,
      context: null,
      stars: [], //星星数组
      shadowColorList: [
        "#39f",
        "#ec5707",
        "#b031d4",
        "#22e6c7",
        "#92d819",
        "#14d7f1",
        "#e23c66",
      ], //阴影颜色列表
      directionList: ["leftTop", "leftBottom", "rightTop", "rightBottom"], //星星运行方向
      speed: 100, //星星运行速度
      last_star_created_time: new Date(), //上次重绘星星时间
      Ball: class Ball {
        constructor(radius) {
          this.x = 0;
          this.y = 0;
          this.radius = radius;
          this.color = "";
          this.shadowColor = "";
          this.direction = "";
        }

        draw(context) {
          context.save();
          context.translate(this.x, this.y);
          context.lineWidth = this.lineWidth;
          var my_gradient = context.createLinearGradient(0, 0, 0, 8);
          my_gradient.addColorStop(0, this.color);
          my_gradient.addColorStop(1, this.shadowColor);
          context.fillStyle = my_gradient;
          context.beginPath();
          context.arc(0, 0, this.radius, 0, Math.PI * 2, true);
          context.closePath();

          context.shadowColor = this.shadowColor;
          context.shadowOffsetX = 0;
          context.shadowOffsetY = 0;
          context.shadowBlur = 10;

          context.fill();
          context.restore();
        }
      }, //工厂模式定义Ball类
      width: window.innerWidth,
      height: window.innerHeight,
      loginForm: {
        userName: "",
        passWord: "",
        yzm: "",
      },
      loginRules: {
        userName: [
          { required: true, message: "请输入用户名", trigger: "blur" },
        ],
        passWord: [{ required: true, message: "请输入密码", trigger: "blur" }],
        yzm: [
          { required: true, message: "请输入验证码", trigger: "blur" },
          {
            validator: isTrue,
            trigger: "blur",
          },
        ],
      },
    };
  },
  methods: {
    retrievePWD() {
      this.$router.push({ path: "/retrievePassword" });
    },
    // 生成4个随机数
    createdCode() {
      const len = 4;
      const codeList = [];
      const chars = "ABCDEFGHJKMNPQRSTWXYZabcdefhijkmnprstwxyz0123456789";
      const charsLen = chars.length;
      for (let i = 0; i < len; i++) {
        codeList.push(chars.charAt(Math.floor(Math.random() * charsLen)));
      }
      this.identifyCode = codeList.join("");
      this.identifyCode;
      this.$emit("getIdentifyCode", this.identifyCode.toLowerCase());
      this.drawPic();
    },

    // 生成一个随机数
    randomNum(min, max) {
      return Math.floor(Math.random() * (max - min) + min);
    },
    // 生成一个随机的颜色
    randomColor(min, max) {
      const r = this.randomNum(min, max);
      const g = this.randomNum(min, max);
      const b = this.randomNum(min, max);
      return "rgb(" + r + "," + g + "," + b + ")";
    },

    drawPic() {
      const canvas = document.getElementById("s-canvas");
      const ctx = canvas.getContext("2d");
      ctx.textBaseline = "bottom";
      // 绘制背景
      ctx.fillStyle = this.randomColor(
        this.backgroundColorMin,
        this.backgroundColorMax
      );
      ctx.fillRect(0, 0, this.contentWidth, this.contentHeight);
      // 绘制文字
      for (let i = 0; i < this.identifyCode.length; i++) {
        this.drawText(ctx, this.identifyCode[i], i);
      }
      this.drawLine(ctx);
      this.drawDot(ctx);
    },

    drawText(ctx, txt, i) {
      ctx.fillStyle = this.randomColor(this.colorMin, this.colorMax);
      ctx.font =
        this.randomNum(this.fontSizeMin, this.fontSizeMax) + "px SimHei";
      const x = (i + 1) * (this.contentWidth / (this.identifyCode.length + 1));
      const y = this.randomNum(this.fontSizeMax, this.contentHeight - 5);
      var deg = this.randomNum(-45, 45);
      // 修改坐标原点和旋转角度
      ctx.translate(x, y);
      ctx.rotate((deg * Math.PI) / 180);
      ctx.fillText(txt, 0, 0);
      // 恢复坐标原点和旋转角度
      ctx.rotate((-deg * Math.PI) / 180);
      ctx.translate(-x, -y);
    },

    // 绘制干扰线
    drawLine(ctx) {
      for (let i = 0; i < 5; i++) {
        ctx.strokeStyle = this.randomColor(
          this.lineColorMin,
          this.lineColorMax
        );
        ctx.beginPath();
        ctx.moveTo(
          this.randomNum(0, this.contentWidth),
          this.randomNum(0, this.contentHeight)
        );
        ctx.lineTo(
          this.randomNum(0, this.contentWidth),
          this.randomNum(0, this.contentHeight)
        );
        ctx.stroke();
      }
    },

    // 绘制干扰点
    drawDot(ctx) {
      for (let i = 0; i < 80; i++) {
        ctx.fillStyle = this.randomColor(0, 255);
        ctx.beginPath();
        ctx.arc(
          this.randomNum(0, this.contentWidth),
          this.randomNum(0, this.contentHeight),
          1,
          0,
          2 * Math.PI
        );
        ctx.fill();
      }
    },
    handleClick(tab, event) {
      tab = event;
    },
    //提交登录
    submitForm(formName) {
      const url = "stroll/login";
      const params = `user=${this.loginForm.userName}&pwd=${this.loginForm.passWord}&roles=${this.value}`;
      this.$refs[formName].validate((valid) => {
        if (valid) {
          console.log(valid);
        }
      });
      this.axios.post(url, params).then((res) => {
        if (res.data.length == 0) {
          this.$message("账号或密码错误");
        } else if (this.loginForm.yzm != this.identifyCode) {
          this.$message("验证码错误");
        } else if (this.value == "商家" && res.data.length) {
          if (res.data[0].isTrue == 1) {
            this.$store.commit("saveshopId", res.data[0].shopId);
            this.$store.commit("saveUser", res.data[0].user_name);
            this.fullscreenLoading = true;
            setTimeout(() => {
              this.$message("欢迎登录！");
              this.fullscreenLoading = false;
              this.$router.push("/store");
            }, 1000);
          } else {
            this.$message("管理员审核中，请等待管理员通过！");
          }
        } else if (this.value == "管理员" && res.data.length) {
          this.fullscreenLoading = true;
          setTimeout(() => {
            this.fullscreenLoading = false;
            this.$router.push("/manage");
          }, 1000);
        }
      });
    },
    //重复动画
    drawFrame() {
      this.context.clearRect(0, 0, this.canvas.width, this.canvas.height);
      this.createStar(false);
      this.stars.forEach(this.moveStar);
    },
    //展示所有的星星
    createStar(params) {
      let now = new Date();
      if (params) {
        //初始化星星
        for (let i = 0; i < 50; i++) {
          const radius = Math.random() * 3 + 2;
          let star = new this.Ball(radius);
          star.x = Math.random() * this.canvas.width + 1;
          star.y = Math.random() * this.canvas.height + 1;
          star.color = "#ffffff";
          star.shadowColor =
            this.shadowColorList[
              Math.floor(Math.random() * this.shadowColorList.length)
            ];
          star.direction =
            this.directionList[
              Math.floor(Math.random() * this.directionList.length)
            ];
          this.stars.push(star);
        }
      } else if (!params && now - this.last_star_created_time > 3000) {
        //每隔3秒重绘修改颜色其中30个球阴影颜色
        for (let i = 0; i < 30; i++) {
          this.stars[i].shadowColor =
            this.shadowColorList[
              Math.floor(Math.random() * this.shadowColorList.length)
            ];
        }
        this.last_star_created_time = now;
      }
    },
    //移动
    moveStar(star) {
      if (star.y - this.canvas.height > 0) {
        //触底
        if (Math.floor(Math.random() * 2) === 1) {
          star.direction = "leftTop";
        } else {
          star.direction = "rightTop";
        }
      } else if (star.y < 2) {
        //触顶
        if (Math.floor(Math.random() * 2) === 1) {
          star.direction = "rightBottom";
        } else {
          star.direction = "leftBottom";
        }
      } else if (star.x < 2) {
        //左边
        if (Math.floor(Math.random() * 2) === 1) {
          star.direction = "rightTop";
        } else {
          star.direction = "rightBottom";
        }
      } else if (star.x - this.canvas.width > 0) {
        //右边
        if (Math.floor(Math.random() * 2) === 1) {
          star.direction = "leftBottom";
        } else {
          star.direction = "leftTop";
        }
      }
      if (star.direction === "leftTop") {
        star.y -= star.radius / this.speed;
        star.x -= star.radius / this.speed;
      } else if (star.direction === "rightBottom") {
        star.y += star.radius / this.speed;
        star.x += star.radius / this.speed;
      } else if (star.direction === "leftBottom") {
        star.y += star.radius / this.speed;
        star.x -= star.radius / this.speed;
      } else if (star.direction === "rightTop") {
        star.y -= star.radius / this.speed;
        star.x += star.radius / this.speed;
      }
      star.draw(this.context);
    },
  },
  mounted() {
    this.createdCode();
    this.canvas = document.getElementById("myCanvas");
    this.context = this.canvas.getContext("2d");
    this.createStar(true);
    this.drawFrame();
  },
};
</script>
<style>
.el-input__inner {
  color: black !important;
}
#model-box {
  position: fixed;
  left: 0;
  top: 0;
  right: 0;
  bottom: 0;
  background-color: rgba(0, 0, 0, 0.2);
  display: flex;
  justify-content: center;
  align-items: center;
}

#center {
  width: 300px;
  height: 150px;
  background-color: #fff;
  display: flex;
  flex-direction: column;
  justify-content: space-evenly;
}

#center div {
  text-align: center;
}

#loginBox .el-tabs__item {
  width: 180px;
}
</style>
<style lang="less" scoped>
.id_select {
  opacity: 0.7;
  color: white;
}

.id_select::placeholder {
  color: black;
}
.a,
.c {
  display: flex;
}

#login {
  width: 100vw;
  padding: 0;
  margin: 0;
  height: 100vh;
  font-size: 16px;
  background-repeat: no-repeat;
  background-position: left top;
  background-color: #04010c3a; //242645  5f627f
  color: #fff;
  font-family: "Source Sans Pro";
  background-size: 100%;
  background-image: url("../../assets/img/login/mask.png");
  position: relative;
  #bgd {
    height: 100vh;
    width: 100vw;
    overflow: hidden;
  }
  #loginBox {
    text-align: center;
    width: 360px;
    height: 500px;
    position: absolute;
    top: 0;
    left: 0;
    right: 0;
    bottom: 0;
    margin: auto;

    padding: 50px 40px 40px 40px;
    box-shadow: -15px 15px 15px rgba(6, 17, 47, 0.7);
    opacity: 0.8;

    background: linear-gradient(
      230deg,
      rgba(0, 0, 0, 0) 0%,
      rgb(67, 67, 67) 100%
    );

    /deep/ .inps input {
      border: none;
      color: #fff;
      background-color: transparent;
      font-size: 15px;
    }
    /deep/ .yzm input {
      border: none;
      color: #fff;
      background-color: transparent;
      font-size: 15px;
      width: 200px;
    }
    .submitBtn {
      background-color: transparent;
      color: #39f;
      width: 200px;
      margin-top: -80px;
    }
    .iconfont {
      color: #fff;
      // size: 30px;
    }
  }
}
</style>
